package com.meilai.project.mapper.business.sale;

import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.meilai.project.dto.business.installOrder.WorkOrderBillSaleDTO;
import com.meilai.project.dto.business.sale.BillSaleListDTO;
import com.meilai.project.dto.business.sale.SaleBillListDTO;
import com.meilai.project.entity.business.sale.BillSale;
import com.meilai.project.entity.media.MediaType;
import com.meilai.project.vo.app.CompanyOfflineWorkOrderProcessingContractDataVO;
import com.meilai.project.vo.app.CompanyOfflineWorkOrderProcessingContractDateRangeDataVO;
import com.meilai.project.vo.business.contract.ContractMediaCountDTO;
import com.meilai.project.vo.business.installOrder.Id2PointIdVO;
import com.meilai.project.vo.business.installOrder.WorkOrderBillSaleVO;
import com.meilai.project.vo.business.sale.BillSaleVO;
import com.meilai.project.vo.business.sale.BillSaleVO2;
import com.meilai.project.vo.business.sale.SaleBillVO;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select;
import org.apache.ibatis.annotations.Update;

import java.math.BigDecimal;
import java.time.LocalDate;
import java.util.List;
import java.util.Set;

/**
 * <p>
 * Mapper 接口
 * </p>
 *
 * @author xchen
 * @since 2022-03-19
 */
@Mapper
public interface BillSaleMapper extends BaseMapper<BillSale> {

    List<Id2PointIdVO> listBillSaleMediaPoint(@Param("ids") List<Long> billSaleIdList);

    @Select("<script>" +
            "SELECT  " +
            "d.id AS work_order_id " +
            ",a.id AS contract_id " +
            ",CONCAT(b.part_a, DATE_FORMAT(c.start_at,'%Y-%m-%d'), '~', DATE_FORMAT(c.end_at,'%Y-%m-%d')) AS `name` " +
            "FROM  " +
            "bill_sale a " +
            "JOIN contract_apply b ON a.contract_id=b.id " +
            "JOIN media_point_choose_daterange c ON a.daterange_id=c.id " +
            "JOIN work_order d ON a.id=d.bill_sale_id " +
            "WHERE d.id IN " +
            "<foreach item=\"item\" index=\"index\" collection=\"workOrderIds\" open=\"(\" separator=\",\" close=\")\"> " +
            "#{item}" +
            "</foreach>" +
            "UNION " +
            "SELECT  " +
            "d.id AS work_order_id " +
            ",bs.id AS contract_id " +
            ",CONCAT(b.part_a, DATE_FORMAT(c.start_at,'%Y-%m-%d'), '~', DATE_FORMAT(c.end_at,'%Y-%m-%d')) AS `name` " +
            "FROM  " +
            "bill_market_detail a " +
            "JOIN bill_sale bs ON a.bill_sale_id = bs.id " +
            "JOIN contract_apply b ON bs.contract_id=b.id " +
            "JOIN media_point_choose_daterange c ON a.daterange_id=c.id " +
            "JOIN work_order d ON a.id=d.bill_sale_id " +
            "WHERE d.id IN " +
            "<foreach item=\"item\" index=\"index\" collection=\"workOrderIds\" open=\"(\" separator=\",\" close=\")\"> " +
            "#{item}" +
            "</foreach>" +
            "</script>")
    List<CompanyOfflineWorkOrderProcessingContractDataVO> queryContractsForApp(@Param("workOrderIds") Set<Long> workOrderIds);

    @Select("<script>" +
            "SELECT  " +
            "d.id AS work_order_id " +
            ",a.id AS contract_id " +
            ",c.id AS date_range_id " +
            ",c.start_at " +
            ",c.end_at " +
            "FROM  " +
            "bill_sale a " +
            "JOIN contract_apply b ON a.contract_id=b.id " +
            "JOIN media_point_choose_daterange c ON a.daterange_id=c.id " +
            "JOIN work_order d ON a.id=d.bill_sale_id " +
            "WHERE d.id IN " +
            "<foreach item=\"item\" index=\"index\" collection=\"workOrderIds\" open=\"(\" separator=\",\" close=\")\"> " +
            "#{item}" +
            "</foreach> " +
            "UNION " +
            "SELECT  " +
            "d.id AS work_order_id " +
            ",bs.id AS contract_id " +
            ",c.id AS date_range_id " +
            ",c.start_at " +
            ",c.end_at " +
            "FROM  " +
            "bill_market_detail a " +
            "JOIN bill_sale bs ON a.bill_sale_id = bs.id " +
            "JOIN contract_apply b ON bs.contract_id=b.id " +
            "JOIN media_point_choose_daterange c ON a.daterange_id=c.id " +
            "JOIN work_order d ON a.id=d.bill_market_detail_id " +
            "WHERE d.id IN " +
            "<foreach item=\"item\" index=\"index\" collection=\"workOrderIds\" open=\"(\" separator=\",\" close=\")\"> " +
            "#{item}" +
            "</foreach> " +
            "</script>")
    List<CompanyOfflineWorkOrderProcessingContractDateRangeDataVO> queryDaterangesForApp(@Param("workOrderIds") Set<Long> workOrderIds);

    BillSaleVO getVOById(@Param("id") Long id);

    List<BillSaleVO> getVOListByIds(@Param("ids") List<Long> ids);

    List<BillSaleVO> getChangedVOListByIds(@Param("ids") Set<Long> ids);

    List<BillSaleVO> selectPageList(Page<BillSaleVO> page, @Param("query") BillSaleListDTO searchDTO);

    List<BillSaleVO> listForMarketByContractId(@Param("contractId") Long contractId,
                                               @Param("mustIncludeBillSaleId") Long mustIncludeBillSaleId,
                                               @Param("type") Integer type);

    List<WorkOrderBillSaleVO> selectPageListBillSaleForWorkorder(Page<WorkOrderBillSaleVO> page, @Param("searchDTO") WorkOrderBillSaleDTO workOrderBillSaleDTO);

    List<BillSaleVO2> dispatchList(@Param("page") Page<BillSaleVO2> page, @Param("query") BillSaleListDTO searchDTO);

    List<String> getMediaFormByDateRangeId(@Param("dateRangeId") Long dateRangeId);

    void updateMode(@Param("chooseIdList") List<Long> chooseIdList, @Param("hangUp") Integer status);

    List<BillSale> listByChooseIds(@Param("chooseIdList") List<Long> chooseIdList);

    @Update("update bill_sale set contract_id = #{newContractId} where contract_id = #{oldContractId}")
    void update(@Param("oldContractId") Long oldContractId, @Param("newContractId") Long newContractId);

    int confirmMonitor(@Param("id") Long id);

    int updateAccruedAmount(@Param("accrued_amount") BigDecimal accrued_amount, @Param("id") Long id);

    List<MediaType> getMediaTypeArrBySaleId(@Param("id") Long id);

    List<BillSaleVO> selectListOfIds(@Param("ids") List<Long> ids);

    List<BillSaleVO> list_by_user_id(@Param("user_id") Long user_id);

    int updateDate(@Param("date") LocalDate date, @Param("ids") List<Long> ids);

    List<Long> getFullPaymentBillSaleIds();

    int updateReminderDate(@Param("date") LocalDate date, @Param("ids") List<Long> ids);

    /**
     * 查询对应的资源类型和数量
     * @param ins_ids 方案ids
     */
    List<ContractMediaCountDTO> getMediaTypeCount(@Param("ins_ids") Set<Long> ins_ids);

    /*============================NEW ADD============================*/
    SaleBillVO getSingleVOById(@Param("id") Long id);
    List<SaleBillVO> selectNewPageList(Page<SaleBillVO> page, @Param("query") SaleBillListDTO searchDTO);
    @Select("SELECT SUM(execute_amount) FROM bill_sale WHERE contract_id = #{contractId} AND flow_status IN (3,4) AND mode = 0")
    BigDecimal sumExecutedMoney(@Param("contractId") Long contractId);

    List<SaleBillVO> listLatestSaleBill(@Param("deptId") Long deptId,
                                        @Param("contractId") Long contractId,
                                        @Param("mustIncludeBillSaleId") Long mustIncludeBillSaleId,
                                        @Param("type") Integer type);

}
